/* **********************************************************************************
 *
 * Copyright (c) TMF.AscendedThemeKit.Unthemed.NET Project. All rights reserved.
 *
 * This source code is subject to terms and conditions of the Shared Source License
 * for TMF.AscendedThemeKit.Unthemed. A copy of the license can be found in the License.html file
 * at the root of this distribution. If you can not locate the Shared Source License
 * for TMF.AscendedThemeKit.Unthemed, please send an email to ascend_adm@hotmail.com.
 * By using this source code in any fashion, you are agreeing to be bound by
 * the terms of the Shared Source License for TMF.AscendedThemeKit.Unthemed.NET.
 *
 * You must not remove this notice, or any other, from this software.
 *
 * **********************************************************************************/

using TMF.AscendedThemeKit.Unthemed.Resources;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Drawing;
using System.Drawing.Design;
using System.Text;
using System.Windows.Forms;
using System.ComponentModel.Design;

namespace TMF.AscendedThemeKit.Unthemed.Windows.Forms
{
    /// <summary>
    /// Used to groups collections of controls in NavigationPane.
    /// </summary>
    [DesignTimeVisible(true)]
#if GENERAL_RELEASE
    [Designer(typeof(Ascend.Windows.Forms.Design.NavigationPanePageDesigner), typeof(IDesigner))]
#else
    [Designer("TMF.AscendedThemeKit.Unthemed.Windows.Forms.Design.NavigationPanePageDesigner, TMF.AscendedThemeKit.Unthemed.Design.v1.5, Culture=neutral, PublicKeyToken=5123e2ac4258b06a", typeof(IDesigner))]
#endif
    [DesignerCategory("Form")]
    [ToolboxItem(false)]
    public class NavigationPanePage : ContainerControl
    {
        private NavigationPanePageRender _render;
        private Rectangle _buttonRectangle;
        private bool _active;
        private Image _image;
        private Image _imageFooter;
        private bool _buttonVisible;
        private int _imageIndex;
        private int _imageIndexFooter;
        private string _imageKey = string.Empty;
        private string _imageKeyFooter = string.Empty;
        private ImageList _imageList;
        private ImageList _imageListFooter;
        private bool _minimized;
        private string _toolTipText;
        private bool _minimizedVisible;        
        private int _displayOrder;
        private string _key;
        private ContentAlignment _textAlign;
        private ContentAlignment _imageAlign;
        private NavigationPanePageButtonProperty _buttonProperty;
        private NavigationPanePageFooterProperty _footerProperty;

        /// <summary>
        /// Occurs when the Active property changes. 
        /// </summary>
        [ResourceDescriptionAttribute("ActiveChangedEventDescription"), ResourceCategoryAttribute("PropertyChangedCategory"), ResourceDisplayName("DisplayNameActiveChanged")]
        public event EventHandler ActiveChanged;

        /// <summary>
        /// Occurs when the ImageAlign property changes.
        /// </summary>
        [ResourceDescriptionAttribute("ImageAlignChangedEventDescription"), ResourceCategoryAttribute("PropertyChangedCategory"), ResourceDisplayName("DisplayNameImageAlignChanged")]
        public event EventHandler ImageAlignChanged;

        /// <summary>
        /// Occurs when the ImageIndex property changes. 
        /// </summary>
        [ResourceDescriptionAttribute("ImageIndexChangedEventDescription"), ResourceCategoryAttribute("PropertyChangedCategory"), ResourceDisplayName("DisplayNameImageIndexChanged")]
        public event EventHandler ImageIndexChanged;

        /// <summary>
        /// Occurs when the ImageIndexFooter property changes. 
        /// </summary>
        [ResourceDescriptionAttribute("ImageIndexFooterChangedEventDescription"), ResourceCategoryAttribute("PropertyChangedCategory"), ResourceDisplayName("DisplayNameImageIndexFooterChanged")]
        public event EventHandler ImageIndexFooterChanged;

        /// <summary>
        /// Occurs when the TextAlign property changes on the navigation button.
        /// </summary>
        [ResourceDescriptionAttribute("TextAlignChangedEventDescription"), ResourceCategoryAttribute("PropertyChangedCategory"), ResourceDisplayName("DisplayNameTextAlignChanged")]
        public event EventHandler TextAlignChanged;


        /// <summary>
        /// Occurs when the ActiveGradientLowColor property changes. 
        /// </summary>
        [ResourceDescriptionAttribute("ActiveGradientLowColorEventDescription"), ResourceCategoryAttribute("PropertyChangedCategory"), ResourceDisplayName("DisplayNameActiveGradientLowColorChanged")]
        public event EventHandler ActiveGradientLowColorChanged;

        /// <summary>
        /// Gets or sets the text associated with this control's button. 
        /// </summary>
        /// <value>
        /// The text associated with this control's text. 
        /// </value>
        [Browsable(false)]
        public override string Text
        {
            get
            {
                return base.Text;

            }

            set
            {
                base.Text = value;

                if (this.Parent != null)
                {
                    this.Parent.Invalidate();
                    this.Parent.Update();

                }

            }

        }

        /// <summary>
        /// The ContentAlignment associated with this controls text.
        /// </summary>
        /// <value>
        /// <para>
        /// System.Drawing.ContentAlignment . The ContentAlignment associated with this controls text.
        /// </para>
        /// <para>
        /// This property is read/write. 
        /// </para>
        /// </value>
        [Browsable(false)]
        public ContentAlignment TextAlign
        {
            get
            {
                return this._textAlign;

            }

            set
            {
                if (value == this._textAlign)
                {
                    return;

                }

                this._textAlign = value;

                if (this.Parent != null)
                {
                    this.Parent.Invalidate();

                }

                this.OnTextAlignChanged(new EventArgs());

            }

        }

        private bool IsTextAlignCustomized()
        {
            if (this.Parent != null)
            {
                NavigationPane parentNavigationPane = this.Parent as NavigationPane;

                if (parentNavigationPane != null)
                {
                    if (parentNavigationPane.ButtonTextAlign == this._textAlign)
                    {
                        return false;

                    }
                    else
                    {
                        return true;

                    }

                }
                else
                {
                    return true;

                }

            }
            else
            {
                return true;

            }

        }

        /// <summary>
        /// Determines if the TextAlign property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>always true</returns>
        public bool ShouldSerializeTextAlign()
        {
            return true;

        }

        /// <summary>
        /// Gets or sets the button rectangle
        /// </summary>
        [Browsable(false), DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
        public Rectangle ButtonRectangle
        {
            get
            {
                return this._buttonRectangle;

            }

            set
            {
                this._buttonRectangle = value;

            }

        }

        /// <summary>
        /// Specifies if the control is currently active (has focus or is selected).
        /// </summary>
        /// <value>
        /// 	<para>
        /// System.Boolean . Specifies if the control is currently active (has focus or is selected).
        /// </para>
        /// 	<para>
        /// This property is read/write. 
        /// </para>
        /// </value>
        [Browsable(false), DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
        public virtual bool Active
        {
            get
            {
                return this._active;

            }

            set
            {
                if (value == this._active)
                {
                    return;

                }

                this._active = value;

                this.OnActiveChanged(new EventArgs());

            }

        }

        /// <summary>
        /// The image associated with this control's button.
        /// </summary>
        /// <value>
        /// 	<para>
        /// System.Drawing.Image . The image associated with this control's button.
        /// </para>
        /// 	<para>
        /// This property is read/write. 
        /// </para>
        /// </value>
        [Browsable(false)]
        public Image Image
        {
            get
            {
                if ((this._image == null) && (this._imageList != null))
                {
                    if (this._imageIndex != -1)
                    {
                        int imageIndex = this._imageIndex;
                        if (imageIndex >= this._imageList.Images.Count)
                        {
                            imageIndex = this._imageList.Images.Count - 1;

                        }

                        if (imageIndex >= 0)
                        {
                            return this._imageList.Images[imageIndex];

                        }

                    }
                    else
                    {
                        if ((this._imageKey != null) && (this._imageKey.Length > 0))
                        {
                            string imageKey = this._imageKey;

                            if (!this._imageList.Images.ContainsKey(imageKey))
                            {
                                int imageIndex = this._imageList.Images.Count - 1;

                                if (imageIndex >= 0)
                                {
                                    return this._imageList.Images[imageIndex];

                                }

                            }
                            else
                            {
                                return this._imageList.Images[imageKey];

                            }

                        }

                    }

                }

                return this._image;

            }

            set
            {
                if (this._image != value)
                {
                    this._image = value;

                    if (this._image != null)
                    {
                        this._imageIndex = -1;
                        this._imageKey = string.Empty;
                        this._imageList = null;

                    }

                    if (this.Parent != null)
                    {
                        this.Parent.Invalidate();
                        this.Parent.Update();

                    }

                }

            }

        }

        /// <summary>
        /// The ContentAlignment associated with this controls image.
        /// </summary>
        /// <value>
        /// <para>
        /// System.Drawing.ContentAlignment . The ContentAlignment associated with this controls image.
        /// </para>
        /// <para>
        /// This property is read/write. 
        /// </para>
        /// </value>
        [Browsable(false)]
        public ContentAlignment ImageAlign
        {
            get
            {
                return this._imageAlign;

            }

            set
            {
                if (value == this._imageAlign)
                {
                    return;

                }

                this._imageAlign = value;

                if (this.Parent != null)
                {
                    this.Parent.Invalidate();

                }

                this.OnImageAlignChanged(new EventArgs());

            }

        }

        private bool IsImageAlignCustomized()
        {
            if (this.Parent != null)
            {
                NavigationPane parentNavigationPane = this.Parent as NavigationPane;

                if (parentNavigationPane != null)
                {
                    if (parentNavigationPane.ButtonImageAlign == this._imageAlign)
                    {
                        return false;

                    }
                    else
                    {
                        return true;

                    }

                }
                else
                {
                    return true;

                }

            }
            else
            {
                return true;

            }

        }

        /// <summary>
        /// Determines if the ImageAlign property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>always true</returns>
        public bool ShouldSerializeImageAlign()
        {
            return true;

        }

        /// <summary>
        /// The image associated with this control when it is minimized to the footer.
        /// </summary>
        /// <value>
        /// 	<para>
        /// System.Drawing.Image . The image associated with this control when it is minimized to the footer.
        /// </para>
        /// 	<para>
        /// This property is read/write. 
        /// </para>
        /// </value>
        [Browsable(false)]
        public Image ImageFooter
        {
            get
            {
                if ((this._imageFooter == null) && (this._imageListFooter != null))
                {
                    if (this._imageIndexFooter != -1)
                    {
                        int imageIndex = this._imageIndexFooter;
                        if (imageIndex >= this._imageListFooter.Images.Count)
                        {
                            imageIndex = this._imageListFooter.Images.Count - 1;

                        }

                        if (imageIndex >= 0)
                        {
                            return this._imageListFooter.Images[imageIndex];

                        }

                    }
                    else
                    {
                        if ((this._imageKeyFooter != null) && (this._imageKeyFooter.Length > 0))
                        {
                            string imageKey = this._imageKeyFooter;

                            if (!this._imageListFooter.Images.ContainsKey(imageKey))
                            {
                                int imageIndex = this._imageListFooter.Images.Count - 1;

                                if (imageIndex >= 0)
                                {
                                    return this._imageListFooter.Images[imageIndex];

                                }

                            }
                            else
                            {
                                return this._imageListFooter.Images[imageKey];

                            }

                        }

                    }

                }

                return this._imageFooter;

            }

            set
            {
                if (this._imageFooter != value)
                {
                    this._imageFooter = value;

                    if (this._imageFooter != null)
                    {
                        this._imageIndexFooter = -1;
                        this._imageKeyFooter = string.Empty;
                        this._imageListFooter = null;

                    }

                    if (this.Parent != null)
                    {
                        this.Parent.Invalidate();
                        this.Parent.Update();

                    }

                }

            }

        }

        /// <summary>
        /// Is the button minimized.
        /// </summary>
        [Browsable(false), DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
        public bool ButtonMinimized
        {
            get
            {
                return this._minimized;

            }

            set
            {
                this._minimized = value;

            }

        }

        /// <summary>
        /// Gets or sets a value indicating whether the page navigation button is displayed. 
        /// </summary>
        /// <value>
        /// true if the navigation button is displayed; otherwise, false. The default is true.
        /// </value>
        [ResourceDescriptionAttribute("NPButtonVisibleDescription"), ResourceCategoryAttribute("BehaviorCategory"), ResourceDisplayName("DisplayNameButtonVisible"), DefaultValueAttribute(true), RefreshProperties(RefreshProperties.Repaint)]
        public bool ButtonVisible
        {
            get
            {
                return this._buttonVisible;

            }

            set
            {
                this._buttonVisible = value;

            }

        }

        /// <summary>
        /// Gets or set button active gradient high color.
        /// </summary>
        [Browsable(false)]
        public Color ActiveGradientHighColor
        {
            get
            {
                return this._render.ButtonActiveGradientHighColor;

            }

            set
            {
                if (this._render.ButtonActiveGradientHighColor == value)
                {
                    return;

                }

                this._render.ButtonActiveGradientHighColor = value;

                base.Invalidate();

                if (this.Parent != null)
                {
                    this.Parent.Invalidate();

                }

            }

        }

        /// <summary>
        /// Determines if the ActiveGradientHighColor property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>always true</returns>
        public bool ShouldSerializeActiveGradientHighColor()
        {
            return true;

        }

        private bool IsActiveGradientHighColorCustomized()
        {
            if (this.Parent != null)
            {
                NavigationPane parentNavigationPane = this.Parent as NavigationPane;

                if (parentNavigationPane != null)
                {
                    if (parentNavigationPane.ButtonActiveGradientHighColor == this.ActiveGradientHighColor)
                    {
                        return false;

                    }
                    else
                    {
                        return true;

                    }

                }
                else
                {
                    return true;

                }

            }
            else
            {
                return true;

            }

        }

        /// <summary>
        /// Gets or set button active gradient low color.
        /// </summary>
        [Browsable(false)]
        public Color ActiveGradientLowColor
        {
            get
            {
                
                return this._render.ButtonActiveGradientLowColor;

            }

            set
            {
                if (this._render.ButtonActiveGradientLowColor == value)
                {
                    return;

                }

                this._render.ButtonActiveGradientLowColor = value;

                base.Invalidate();

                if (this.Parent != null)
                {
                    this.Parent.Invalidate();

                }

            }

        }

        /// <summary>
        /// Determines if the ActiveGradientLowColor property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>always true</returns>
        public bool ShouldSerializeActiveGradientLowColor()
        {
            return true;

        }

        private bool IsActiveGradientLowColorCustomized()
        {
            if (this.Parent != null)
            {
                NavigationPane parentNavigationPane = this.Parent as NavigationPane;

                if (parentNavigationPane != null)
                {
                    if (parentNavigationPane.ButtonActiveGradientLowColor == this.ActiveGradientLowColor)
                    {
                        return false;

                    }
                    else
                    {
                        return true;

                    }

                }
                else
                {
                    return true;

                }

            }
            else
            {
                return true;

            }

        }

        /// <summary>
        /// Gets or sets the gradient high (lighter) color for the button when it is moused over.
        /// </summary>
        [Browsable(false)]
        public Color HighlightGradientHighColor
        {
            get
            {
                return this._render.ButtonHighlightGradientHighColor;

            }

            set
            {
                if (this._render.ButtonHighlightGradientHighColor == value)
                {
                    return;

                }

                this._render.ButtonHighlightGradientHighColor = value;

                base.Invalidate();

                if (this.Parent != null)
                {
                    this.Parent.Invalidate();

                }

            }

        }
        
        /// <summary>
        /// Determines if the HighlightGradientHighColor property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>always true</returns>
        public bool ShouldSerializeHighlightGradientHighColor()
        {
            return true;

        }

        private bool IsHighlightGradientHighColorCustomized()
        {
            if (this.Parent != null)
            {
                NavigationPane parentNavigationPane = this.Parent as NavigationPane;

                if (parentNavigationPane != null)
                {
                    if (parentNavigationPane.ButtonHighlightGradientHighColor == this.HighlightGradientHighColor)
                    {
                        return false;

                    }
                    else
                    {
                        return true;

                    }

                }
                else
                {
                    return true;

                }

            }
            else
            {
                return true;

            }

        }

        /// <summary>
        /// Gets or sets the gradient low (darker) color for the button when it is moused over.
        /// </summary>
        [Browsable(false)]
        public Color HighlightGradientLowColor
        {
            get
            {
                return this._render.ButtonHighlightGradientLowColor;

            }

            set
            {
                if (this._render.ButtonHighlightGradientLowColor == value)
                {
                    return;

                }

                this._render.ButtonHighlightGradientLowColor = value;

                base.Invalidate();

                if (this.Parent != null)
                {
                    this.Parent.Invalidate();

                }

            }

        }

        /// <summary>
        /// Determines if the HighlightGradientLowColor property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>always true</returns>
        public bool ShouldSerializeHighlightGradientLowColor()
        {
            return true;

        }

        private bool IsHighlightGradientLowColorCustomized()
        {
            if (this.Parent != null)
            {
                NavigationPane parentNavigationPane = this.Parent as NavigationPane;

                if (parentNavigationPane != null)
                {
                    if (parentNavigationPane.ButtonHighlightGradientLowColor == this.HighlightGradientLowColor)
                    {
                        return false;

                    }
                    else
                    {
                        return true;

                    }

                }
                else
                {
                    return true;

                }

            }
            else
            {
                return true;

            }

        }

        /// <summary>
        /// Gets or sets the button gradient high color on the control.
        /// </summary>
        [Browsable(false)]
        public Color GradientHighColor
        {
            get
            {
                return this._render.ButtonGradientHighColor;

            }

            set
            {
                if (this._render.ButtonGradientHighColor == value)
                {
                    return;

                }

                this._render.ButtonGradientHighColor = value;

                base.Invalidate();

                if (this.Parent != null)
                {
                    this.Parent.Invalidate();

                }

            }

        }

        /// <summary>
        /// Determines if the GradientHighColor property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>always true</returns>
        public bool ShouldSerializeGradientHighColor()
        {
            return true;

        }

        private bool IsButtonGradientHighColorCustomized()
        {
            if (this.Parent != null)
            {
                NavigationPane parentNavigationPane = this.Parent as NavigationPane;

                if (parentNavigationPane != null)
                {
                    if (parentNavigationPane.ButtonGradientHighColor == this.GradientHighColor)
                    {
                        return false;

                    }
                    else
                    {
                        return true;

                    }

                }
                else
                {
                    return true;

                }

            }
            else
            {
                return true;

            }

        }

        /// <summary>
        /// Gets or sets the button gradient low color.
        /// </summary>
        [Browsable(false)]
        public Color GradientLowColor
        {
            get
            {
                return this._render.ButtonGradientLowColor;

            }

            set
            {
                if (this._render.ButtonGradientLowColor == value)
                {
                    return;

                }

                this._render.ButtonGradientLowColor = value;

                base.Invalidate();

                if (this.Parent != null)
                {
                    this.Parent.Invalidate();

                }

            }

        }

        /// <summary>
        /// Determines if the GradientLowColor property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>always true</returns>
        public bool ShouldSerializeGradientLowColor()
        {
            return true;

        }

        private bool IsButtonGradientLowColorCustomized()
        {
            if (this.Parent != null)
            {
                NavigationPane parentNavigationPane = this.Parent as NavigationPane;

                if (parentNavigationPane != null)
                {
                    if (parentNavigationPane.ButtonGradientLowColor == this.GradientLowColor)
                    {
                        return false;

                    }
                    else
                    {
                        return true;

                    }

                }
                else
                {
                    return true;

                }

            }
            else
            {
                return true;

            }

        }

        /// <summary>
        /// Gets or sets the font associated with the buttons.
        /// </summary>
        [Browsable(false)]
        public Font ButtonFont
        {
            get
            {
                return this._render.ButtonFont;

            }

            set
            {
                if (this._render.ButtonFont == value)
                {
                    return;

                }

                this._render.ButtonFont = value;

                base.Invalidate();

                if (this.Parent != null)
                {
                    this.Parent.Invalidate();

                }

            }

        }

        /// <summary>
        /// Gets or sets the forecolor associated with the buttons.
        /// </summary>
        [Browsable(false)]
        public Color ButtonForeColor
        {
            get
            {
                return this._render.ButtonForeColor;

            }

            set
            {
                if (this._render.ButtonForeColor == value)
                {
                    return;

                }

                this._render.ButtonForeColor = value;

                base.Invalidate();

                if (this.Parent != null)
                {
                    this.Parent.Invalidate();

                }

            }

        }

        private bool IsButtonForeColorCustomized()
        {
            if (this.Parent != null)
            {
                NavigationPane parentNavigationPane = this.Parent as NavigationPane;

                if (parentNavigationPane != null)
                {
                    if (parentNavigationPane.ButtonForeColor == this.ButtonForeColor)
                    {
                        return false;

                    }
                    else
                    {
                        return true;

                    }

                }
                else
                {
                    return true;

                }

            }
            else
            {
                return true;

            }

        }

        /// <summary>
        /// Determines if the ButtonForeColor property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>always true</returns>
        public bool ShouldSerializeButtonForeColor()
        {
            return true;

        }

        /// <summary>
        /// Gets or sets the image list index value of the image displayed on the control's button. 
        /// </summary>
        [Browsable(false)]
        public int ImageIndex
        {
            get
            {
                if (((this._imageIndex != -1) && (this._imageList != null)) && (this._imageIndex >= this._imageList.Images.Count))
                {
                    return (this._imageList.Images.Count - 1);

                }

                return this._imageIndex;

            }

            set
            {
                if (this._imageIndex != value)
                {
                    if (value != -1)
                    {
                        this._image = null;
                        this._imageKey = string.Empty;

                    }

                    this._imageIndex = value;

                    if (this.Parent != null)
                    {
                        this.Parent.Invalidate();
                        this.Parent.Update();

                    }

                    this.OnImageIndexChanged(new EventArgs());

                }

            }

        }

        /// <summary>
        /// Gets or sets the image list index value of the image displayed on the control when the button is minimized. 
        /// </summary>
        [Browsable(false)]
        public int ImageIndexFooter
        {
            get
            {
                if (((this._imageIndexFooter != -1) && (this._imageListFooter != null)) && (this._imageIndexFooter >= this._imageListFooter.Images.Count))
                {
                    return (this._imageListFooter.Images.Count - 1);

                }

                return this._imageIndexFooter;

            }

            set
            {
                if (this._imageIndexFooter != value)
                {
                    this._imageFooter = null;
                    this._imageKeyFooter = string.Empty;

                    this._imageIndexFooter = value;

                    if (this.Parent != null)
                    {
                        this.Parent.Invalidate();
                        this.Parent.Update();

                    }

                    this.OnImageIndexFooterChanged(EventArgs.Empty);

                }

            }

        }

        /// <summary>
        /// Gets or sets the key associated with the page.
        /// </summary>
        [ResourceDescriptionAttribute("KeyDescription"), ResourceCategoryAttribute("BehaviorCategory"), ResourceDisplayName("DisplayNameKey")]
        public string Key
        {
            get
            {
                return this._key;

            }

            set
            {
                if (this._key != value)
                {
                    if (value != null)
                    {
                        this._key = value;

                    }

                }

            }

        }

        /// <summary>
        /// Gets or sets the space between controls.
        /// </summary>
        /// <value>
        /// A Padding representing the space between controls.
        /// </value>
        /// <remarks>
        /// The margin of this control is managed by the parent NavigationPane.
        /// </remarks>
        [Browsable(false), DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
        public new Padding Margin
        {
            get
            {
                return base.Margin;

            }

            set
            {
                base.Margin = value;

            }

        }

        /// <summary>
        /// Gets or sets the minimum size the form can be resized to. 
        /// </summary>
        /// <value>
        /// A Size that represents the minimum size for the form. 
        /// </value>
        /// <remarks>
        /// The size of this control is controled by the parent NavigationPane.
        /// </remarks>
        [Browsable(false), DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
        public override System.Drawing.Size MinimumSize
        {
            get
            {
                return base.MinimumSize;

            }

            set
            {
                base.MinimumSize = value;

            }

        }

        /// <summary>
        /// Gets or sets the height and width of the control.
        /// </summary>
        /// <value>
        /// The Size that represents the height and width of the control in pixels.
        /// </value>
        /// <remarks>
        /// The size of this control is controled by the parent NavigationPane.
        /// </remarks>
        [EditorBrowsable(EditorBrowsableState.Never), Browsable(false)]
        public new Size Size
        {
            get
            {
                return base.Size;

            }

            set
            {
                base.Size = value;

            }

        }

        /// <summary>
        /// Gets or sets the key for the image that is displayed for the button.
        /// </summary>
        [Browsable(false)]
        public string ImageKey
        {
            get
            {
                if (((!String.IsNullOrEmpty(this._imageKey)) && (this._imageList != null)) && (!this._imageList.Images.ContainsKey(this._imageKey)))
                {
                    return this._imageList.Images.Keys[(this._imageList.Images.Count - 1)];

                }

                return this._imageKey;

            }

            set
            {
                if (this._imageKey != value)
                {
                    if (value != null)
                    {
                        this._image = null;
                        this._imageIndex = -1;

                    }

                    if (value == "(none)")
                    {
                        this._image = null;
                        this._imageIndex = -1;
                        this._imageKey = string.Empty;

                    }
                    else
                    {
                        this._imageKey = value;

                    }

                    if (this.Parent != null)
                    {
                        this.Parent.Invalidate();
                        this.Parent.Update();

                    }

                }

            }

        }

        /// <summary>
        /// Gets or sets the key for the image that is displayed for the buttton when minimized. 
        /// </summary>
        [Browsable(false)]
        public string ImageKeyFooter
        {
            get
            {
                if (((!String.IsNullOrEmpty(this._imageKeyFooter)) && (this._imageListFooter != null)) && (!this._imageListFooter.Images.ContainsKey(this._imageKeyFooter)))
                {
                    return this._imageListFooter.Images.Keys[(this._imageListFooter.Images.Count - 1)];

                }

                return this._imageKeyFooter;

            }

            set
            {
                if (this._imageKeyFooter != value)
                {
                    if (value != null)
                    {
                        this._imageFooter = null;
                        this._imageIndexFooter = -1;

                    }

                    if (value == "(none)")
                    {
                        this._imageFooter = null;
                        this._imageIndexFooter = -1;
                        this._imageKeyFooter = string.Empty;

                    }
                    else
                    {
                        this._imageKeyFooter = value;

                    }

                    if (this.Parent != null)
                    {
                        this.Parent.Invalidate();
                        this.Parent.Update();

                    }

                }

            }

        }

        /// <summary>
        /// Gets or sets the ImageList that contains the Image displayed on the control. 
        /// </summary>
        [Browsable(false)]
        public ImageList ImageList
        {
            get
            {
                return this._imageList;

            }

            set
            {
                if (this._imageList != value)
                {
                    if (value != null)
                    {
                        this._image = null;

                    }

                    this._imageList = value;

                    if (this.Parent != null)
                    {
                        this.Parent.Invalidate();
                        this.Parent.Update();

                    }

                }


            }

        }

        /// <summary>
        /// Gets or sets the ImageList that contains the footer Image displayed on the control. 
        /// </summary>
        [Browsable(false)]
        public ImageList ImageListFooter
        {
            get
            {
                return this._imageListFooter;

            }

            set
            {
                if (this._imageListFooter != value)
                {
                    if (value != null)
                    {
                        this._imageListFooter = null;

                    }

                    this._imageListFooter = value;

                    if (this.Parent != null)
                    {
                        this.Parent.Invalidate();
                        this.Parent.Update();

                    }

                }


            }

        }

        /// <summary>
        /// 
        /// </summary>
        [EditorBrowsable(EditorBrowsableState.Never), Browsable(false)]
        public new Point Location
        {
            get
            {
                return base.Location;

            }

            set
            {
                base.Location = value;

            }

        }

        /// <summary>
        /// Determines if the Location property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>true or false</returns>
        public bool ShouldSerializeLocation()
        {
            if (base.Left == 0)
            {
                return (base.Top != 0);

            }
            
            return true;

        }

        /// <summary>
        /// The tooltip text to display when the button is minimized.
        /// </summary>
        [Browsable(false)]
        public string ToolTipText
        {
            get
            {
                return this._toolTipText;

            }

            set
            {
                this._toolTipText = value;

            }

        }

        /// <summary>
        /// Sets or returns the specified background color for the style. The default value is Window. 
        /// </summary>
        [ResourceDescriptionAttribute("BackColorDescription"), ResourceCategoryAttribute("AppearanceCategory"), ResourceDisplayName("DisplayNameBackColor"), DefaultValueAttribute(typeof(Color), "Window")]
        public override System.Drawing.Color BackColor
        {
            get
            {
                return base.BackColor;

            }

            set
            {
                base.BackColor = value;

            }

        }

        /// <summary>
        /// Gets or sets the footer properties.
        /// </summary>
        ///         
        [DesignOnlyAttribute(true), EditorBrowsableAttribute(EditorBrowsableState.Never), ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("FooterDescription"), ResourceDisplayName("DisplayNameFooter")]
        public NavigationPanePageFooterProperty Footer
        {
            get
            {
                return this._footerProperty;

            }

            set
            {
                this._footerProperty = value;

            }

        }

        /// <summary>
        /// Determines if the Footer property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>true or false</returns>
        public bool ShouldSerializeFooter()
        {
            if ((this._imageIndexFooter != -1) || (!string.IsNullOrEmpty(this._imageKeyFooter)))
            {
                return true;

            }
            else
            {
                return false;

            }

        }

        /// <summary>
        /// Sets or returns the specified foreground color for the style. Typically, this property sets the color for the text. The default value is WindowText. 
        /// </summary>
        [ResourceDescriptionAttribute("ForeColorDescription"), ResourceCategoryAttribute("AppearanceCategory"), ResourceDisplayName("DisplayNameForeColor"), DefaultValueAttribute(typeof(Color), "WindowText")]
        public override System.Drawing.Color ForeColor
        {
            get
            {
                return base.ForeColor;

            }

            set
            {
                base.ForeColor = value;

            }

        }

        /// <summary>
        /// Gets or sets if the minimized button is visible.
        /// </summary>
        /// <value>
        /// true if the minimized navigation button is displayed; otherwise, false. The default is true.
        /// </value>
        [Browsable(false), DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
        public bool ButtonMinimizedVisible
        {
            get
            {
                return this._minimizedVisible;

            }

            set
            {
                this._minimizedVisible = value;

            }

        }

        /// <summary>
        /// Gets or sets the display (render) order of the button.
        /// </summary>
        [Browsable(false), DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
        public int ButtonDisplayOrder
        {
            get
            {
                return this._displayOrder;

            }

            set
            {
                this._displayOrder = value;

            }

        }

        /// <summary>
        /// Gets or sets the button properties.
        /// </summary>
        ///         
        [DesignOnlyAttribute(true), EditorBrowsableAttribute(EditorBrowsableState.Never), ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("ButtonDescription"), ResourceDisplayName("DisplayNameButton")]
        public NavigationPanePageButtonProperty Button
        {
            get
            {
                return this._buttonProperty;

            }

            set
            {
                this._buttonProperty = value;

            }

        }

        /// <summary>
        /// Determines if the Button property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>true or false</returns>
        public bool ShouldSerializeButton()
        {
            if (this.IsTextAlignCustomized() || this.IsImageAlignCustomized() || this.IsButtonForeColorCustomized() || this.IsButtonGradientHighColorCustomized() || this.IsButtonGradientLowColorCustomized() || this.IsActiveGradientHighColorCustomized() || this.IsActiveGradientLowColorCustomized() || this.IsHighlightGradientHighColorCustomized() || this.IsHighlightGradientLowColorCustomized())
            {
                return true;

            }
            else
            {
                return false;

            }

        }

        /// <summary>
        /// Resets the button to default values.
        /// </summary>
        public void ResetButton()
        {
            if (this.Parent != null)
            {
                NavigationPane navigationPane = this.Parent as NavigationPane;

                if (navigationPane != null)
                {
                    this.ActiveGradientHighColor = navigationPane.ButtonActiveGradientHighColor;
                    this.ActiveGradientLowColor = navigationPane.ButtonActiveGradientLowColor;
                    this.ButtonForeColor = navigationPane.ButtonForeColor;
                    this.GradientHighColor = navigationPane.ButtonGradientHighColor;
                    this.GradientLowColor = navigationPane.ButtonGradientLowColor;
                    this.HighlightGradientHighColor = navigationPane.ButtonHighlightGradientHighColor;
                    this.HighlightGradientLowColor = navigationPane.ButtonHighlightGradientLowColor;
                    this.Image = null;
                    this.ImageAlign = navigationPane.ButtonImageAlign;
                    this.ImageIndex = -1;
                    this.ImageKey = string.Empty;
                    this.TextAlign = navigationPane.ButtonTextAlign;
                    this.ToolTipText = string.Empty;

                }

            }

        }

        /// <summary>
        /// Initializes a new instance of the NavigationPanePage clas.
        /// </summary>
        public NavigationPanePage()
        {
            this.BackColor = SystemColors.Window;
            this.ForeColor = SystemColors.WindowText;
            this._buttonVisible = true;
            this._minimizedVisible = true;
            this._imageIndex = -1;
            this._imageIndexFooter = -1;
            this.AutoScroll = true;
            this._textAlign = ContentAlignment.MiddleLeft;
            this._imageAlign = ContentAlignment.MiddleLeft;
            this._render = new NavigationPanePageRender(this);
            this._buttonProperty = new NavigationPanePageButtonProperty(this);
            this._footerProperty = new NavigationPanePageFooterProperty(this);
            
        }

        /// <summary>
        /// Fires the event indicating that control active property has changed.  Inheriting controls should use this in favour of actually listening to the event, but should not forget to call base.OnActiveChanged() to ensure that the event is still fired for external listeners.
        /// </summary>
        /// <param name="e">A System.EventArgs that contains the event data.</param>
        protected void OnActiveChanged(EventArgs e)
        {
            if (this.ActiveChanged != null)
            {
                this.ActiveChanged(this, e);

            }

        }

        /// <summary>
        /// Fires the event indicating that control image alignment has changed.  Inheriting controls should use this in favour of actually listening to the event, but should not forget to call base.OnImageAlignChanged() to ensure that the event is still fired for external listeners.
        /// </summary>
        /// <param name="e">A System.EventArgs that contains the event data.</param>
        protected virtual void OnImageAlignChanged(EventArgs e)
        {
            if (this.ImageAlignChanged != null)
            {
                this.ImageAlignChanged(this, e);

            }

        }

        private void OnImageIndexChanged(EventArgs e)
        {
            if (this.ImageIndexChanged != null)
            {
                this.ImageIndexChanged(this, e);

            }

        }

        private void OnImageIndexFooterChanged(EventArgs e)
        {
            if (this.ImageIndexFooterChanged != null)
            {
                this.ImageIndexFooterChanged(this, e);

            }

        }

        /// <summary>
        /// Fires the event indicating that control text alignment has changed.  Inheriting controls should use this in favour of actually listening to the event, but should not forget to call base.OnTextAlignChanged() to ensure that the event is still fired for external listeners.
        /// </summary>
        /// <param name="e">A System.EventArgs that contains the event data.</param>
        protected virtual void OnTextAlignChanged(EventArgs e)
        {
            if (this.TextAlignChanged != null)
            {
                this.TextAlignChanged(this, e);

            }

        }


        /// <summary>
        /// Fires the event indicating that control ActiveGradientLowColor property has changed.  Inheriting controls should use this in favour of actually listening to the event, but should not forget to call base.OnActiveGradientLowColorChanged() to ensure that the event is still fired for external listeners.
        /// </summary>
        /// <param name="e">A System.EventArgs that contains the event data.</param>
        protected void OnActiveGradientLowColorChanged(EventArgs e)
        {
            if (this.ActiveGradientLowColorChanged != null)
            {
                this.ActiveGradientLowColorChanged(this, e);

            }

        }

        ////// <summary>
        ////// Called after the control has been added to another container.
        ////// </summary>
        ////// <remarks>
        ////// <para>The InitLayout method is called immediately after adding a control to a container. The InitLayout method enables a control to initialize its layout state based on its container. For example, you would typically apply anchoring and docking to the control in the InitLayout method.</para>
        ////// <para>Notes to Inheritors When overriding InitLayout in a derived class, be sure to call the base class's InitLayout method so that the control is displayed correctly. </para>
        ////// </remarks>
        //////protected override void InitLayout()
        //////{
        //////    if (this.Parent != null)
        //////    {
        //////        NavigationPane navigationPane = this.Parent as NavigationPane;

        //////        if (navigationPane != null)
        //////        {
        //////            this.Bounds = navigationPane.NavigationPageRectangle;

        //////        }

        //////    }

        //////    base.InitLayout();

        //////}

        ///// <summary>
        ///// Performs the work of setting the specified bounds of this control. 
        ///// </summary>
        ///// <param name="x">The new <see cref="P:System.Windows.Forms.Control.Left"></see> property value of the control.</param>
        ///// <param name="y">The new <see cref="P:System.Windows.Forms.Control.Top"></see> property value of the control.</param>
        ///// <param name="width">The new <see cref="P:System.Windows.Forms.Control.Width"></see> property value of the control.</param>
        ///// <param name="height">The new <see cref="P:System.Windows.Forms.Control.Height"></see> property value of the control.</param>
        ///// <param name="specified">A bitwise combination of the <see cref="T:System.Windows.Forms.BoundsSpecified"></see> values.</param>
        //protected override void SetBoundsCore(int x, int y, int width, int height, System.Windows.Forms.BoundsSpecified specified)
        //{
        //    if (this.Parent != null)
        //    {
        //        NavigationPane navigationPane = this.Parent as NavigationPane;
        //        if (navigationPane != null && navigationPane.IsHandleCreated)
        //        {
        //            Rectangle rectangle = navigationPane.NavigationPageRectangle;

        //            base.SetBoundsCore(rectangle.X, rectangle.Y, rectangle.Width, rectangle.Height, (specified == BoundsSpecified.None) ? BoundsSpecified.None : BoundsSpecified.All);

        //        }
        //        else
        //        {
        //            base.SetBoundsCore(x, y, width, height, specified);

        //        }

        //    }
        //    else
        //    {
        //        base.SetBoundsCore(x, y, width, height, specified);

        //    }

        //}

    }

}
